Przypomnienie i dokończenie z poprzednich zajęć:

Biblioteki

Biblioteki dobrze jest wczytywać na początku analizy. Jeśli biblioteka nie jest wczytana próba użycia funkcji należącej do niej zwróci błąd.

Dzisiaj na początek przydadzą nam się poniższe biblioteki.

library(tidyverse)
## ── Attaching core tidyverse packages ──────────────────────── tidyverse 2.0.0 ──
## ✔ dplyr     1.1.3     ✔ readr     2.1.4
## ✔ forcats   1.0.0     ✔ stringr   1.5.0
## ✔ ggplot2   3.5.1     ✔ tibble    3.2.1
## ✔ lubridate 1.9.3     ✔ tidyr     1.3.0
## ✔ purrr     1.0.2     
## ── Conflicts ────────────────────────────────────────── tidyverse_conflicts() ──
## ✖ dplyr::filter() masks stats::filter()
## ✖ dplyr::lag()    masks stats::lag()
## ℹ Use the conflicted package (<http://conflicted.r-lib.org/>) to force all conflicts to become errors
library(gapminder)
library(here)
## here() starts at /Users/golemxiv/Documents/dydaktyka/wizualizacjaR
library(openxlsx)
library(readxl)
library(here)

Wczytywywanie danych

Dane csv

Z użyciem here::here by uniknąć problemów z relatywnymi linkami

panteon <- read_csv(here("podstawy", "panteon_s.csv"))
## Rows: 11341 Columns: 13
## ── Column specification ────────────────────────────────────────────────────────
## Delimiter: ","
## chr (7): name, countryName, countryCode3, continentName, gender, industry, d...
## dbl (6): LAT, LON, birthyear, L_star, HPI, AverageViews
## 
## ℹ Use `spec()` to retrieve the full column specification for this data.
## ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.

Na wszelki wypadek:

#panteon <- read_csv("https://raw.githubusercontent.com/Tomasz-Olczyk/wizualizacjaR/main/podstawy/panteon_s.csv")

Dane excel

Do R można wczytać wiele różncych formatów plików (m. in. Excell, SPSS, Stata, SAS, json, itd. itp.) wykorzystując biblioteki takie jakL openxlsx, readxl, haven i foreign). Biblioteki te mają również funkcje pozwalające zapisać dane w tych formatach.

podatki <- read_excel(
  "../podstawy/Chapter14TablesFigures.xlsx",
  sheet = "TS14.1", #wybieramy arkusz z pliku
 )
## New names:
## • `` -> `...2`
## • `` -> `...3`
## • `` -> `...4`
## • `` -> `...5`
## • `` -> `...6`
## • `` -> `...7`
## • `` -> `...8`
## • `` -> `...9`
## • `` -> `...10`
## • `` -> `...11`
## • `` -> `...12`
## • `` -> `...13`
## • `` -> `...14`
## • `` -> `...15`
podatki <- read_excel(
  "../podstawy/Chapter14TablesFigures.xlsx", #uwaga musimy być we właściwym katalogu roboczym, żeby ta linia kodu zadziałała
  sheet = "TS14.1", #wybieramy arkusz z pliku
  skip = 3 # usuwamy trzy pierwsze wiersze
  )
## New names:
## • `` -> `...1`
## • `` -> `...6`
## • `` -> `...9`
## • `` -> `...11`
## • `` -> `...14`

Lub z użyciem biblioteki here

podatki2 <- read_excel(here("podstawy", "Chapter14TablesFigures.xlsx"), #uwaga musimy być we właściwym katalogu roboczym, żeby ta linia kodu zadziałała
  sheet = "TS14.1", #wybieramy arkusz z pliku
  skip = 3 # usuwamy trzy pierwsze wiersze
  )
## New names:
## • `` -> `...1`
## • `` -> `...6`
## • `` -> `...9`
## • `` -> `...11`
## • `` -> `...14`

Przywoływanie funkcji lub zbioru danych z konkretnej biblioteki operatorem ::

ggplot2::mpg
## # A tibble: 234 × 11
##    manufacturer model      displ  year   cyl trans drv     cty   hwy fl    class
##    <chr>        <chr>      <dbl> <int> <int> <chr> <chr> <int> <int> <chr> <chr>
##  1 audi         a4           1.8  1999     4 auto… f        18    29 p     comp…
##  2 audi         a4           1.8  1999     4 manu… f        21    29 p     comp…
##  3 audi         a4           2    2008     4 manu… f        20    31 p     comp…
##  4 audi         a4           2    2008     4 auto… f        21    30 p     comp…
##  5 audi         a4           2.8  1999     6 auto… f        16    26 p     comp…
##  6 audi         a4           2.8  1999     6 manu… f        18    26 p     comp…
##  7 audi         a4           3.1  2008     6 auto… f        18    27 p     comp…
##  8 audi         a4 quattro   1.8  1999     4 manu… 4        18    26 p     comp…
##  9 audi         a4 quattro   1.8  1999     4 auto… 4        16    25 p     comp…
## 10 audi         a4 quattro   2    2008     4 manu… 4        20    28 p     comp…
## # ℹ 224 more rows

uruchamianie dokumentacji na temat funkcji lub zbioru danych

?mpg  

Funkcja ggplot() warstwy wykresu

Jak działa ggplot?

Istnieje struktalna relacja, mapowanie między zmiennymi w danych a reprezentacją wizualną. W języku ggplota te logiczne połączenia między danymi a elementami wykresu nazywa się mapowaniami estetycznymi (aesthetic mappings).

Tworzenie wykresu zaczyna się od wskazania ggplotowi danych, które posłużą do stworzenia wykresu i jak zmienne z tych danych logicznie łączą się (mapują) z estetykami wykresu.

Nazwa typu wykresu (dokładniej obiektu geometrycznegoe) w ggplot zaczyna się od geom_ i kończy nazwą konkretnego typu np. geom_point dla wykresu punktowego, geom_bar da słupkowego, geom_boxplot dla skrzynkowego itd.

Geometrię, podobnie jak inne warstwy dodajemy +

Funkcja generuje układ współrzędnych, pierwszym argumentem jest zbiór danych na podstawie którego tworzymy wykres:

ggplot(data = mpg)

Żeby powstał prawdziwy wykres dodajemy co najmniej jedną warstwę - funkcję geometryczną np. geom_point

Wszystkie funkcje geometryczne przyjmują argument mapping, definiuje on sposób mapowania zmiennych ze zbioru danych

Argument mapping zawsze wystepuje z funkcją aes().

ggplot(mpg) +
  geom_point()
ggplot(mpg, mapping = aes(x = cty, y = hwy)) +
  geom_point() +
  geom_smooth()
## `geom_smooth()` using method = 'loess' and formula = 'y ~ x'

Kolejność warstw ma znaczenie

ggplot(mpg, aes(x = cty, y = hwy)) +
  geom_smooth() +
geom_point()
## `geom_smooth()` using method = 'loess' and formula = 'y ~ x'

Struktura w ggplot

ggplot(data = <dane>),
      mapping = aes(<estetyka1> = <zmienna1>,
                    <estetyka2> = <zmienna2>)) +
                    geom_<typ>(<...>) +
                    scale_<mapping>_<typ>(<...>)+
                    coord_<typ>(<...>) +
                    labs(<...>)

Argumenty nie muszą być wywoływane jawnie, R w przeważającej liczbie przypadków zrozumie zapis po kolejności argumentów

Terminologia

Funkcje obiektów geometrycznych

Są to obiekty geometryczne opisujące typ tworzonego wykresu. Ich nazwy zawierają przedrostek geom. Wśród nich znajdziemy takie, jak geom_line geom_boxplot czy geom_point, a także dziesiątki innych.

Mapy estetyk

Mapy estetyk (aesthetic mappings) służą do wyznaczania funkcji ggplot pól danych źródłowych, na które mają być rzutowane poszczególne elementy wizualne. Odpowiedzialny za to jest wiersz aes w wywołaniu funkcji ggplot.

Statystyki

Statystykami (ang. stats) nazywane są przekształcenia statystyczne przeprowadzane przed wyświetleniem danych. Nie wszystkie wykresy zawierają statystyki; wśród najpowszechniejszych funkcji związanych ze statystykami są takie, jak stat_edcf, która oblicza dystrybuantę empiryczną, i stat_identity, która sprawia, że dane są przekazywane bez obliczania jakichkolwiek statystyk.

Funkcje fasetowe

Fasetami (ang. facets) to wykresy podrzędne (panelowe, małych wielokrotnosci), prezentujące podzbiór danych. Do funkcjifasetowych należą facet_wrap i facet_grid.

Motywy

Motywami (ang. themes) to elementy wizualne wykresu niepowiązane z danymi. Należą do nich tytuły, marginesy, położenie spisów elementów czy użyte czcionki.

Warstwa

Warstwa (ang. layer) to połączenie danych, map estetyki, obiektu geometrycznego, statysty i innych ustawień tworzących warstwę wizualną wykresu ggplot.

Można zmapować więcej zmiennych używając innych estetyk, np. koloru lub kształtu albo rozmiaru, przroczystości,

ggplot(mpg) +
  geom_point(aes(x = cty, 
                 y = hwy, 
                 alpha = class,
                 color = class,
                 size = class))
## Warning: Using alpha for a discrete variable is not advised.
## Warning: Using size for a discrete variable is not advised.

Zadanie Panteon wykres punktowy

Weźmy poniższe dane

#funkcja subset tworzy podzbiór dancych 
polska <- subset(panteon, countryCode3 == "POL")

Stwórzmy wykres punktowy wykorzystujac dwie wybrane zmienne ilosciowe, na trzecią zmapujmy rozmiar, niech punkty różnią się kolorem w zależności od płci

zadanie - zmapujmy wybraną zmienną na estetykę shape

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, 
                           y = hwy))

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, y = hwy,  alpha = class))
## Warning: Using alpha for a discrete variable is not advised.

ggplot(data = mpg) +
  geom_point(mapping = aes(x = displ, y = hwy))

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, 
                           y = hwy, 
                           alpha = 0.3,
                           color = "blue"))

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, 
                           y = hwy), 
             alpha = 0.3,
             color = "blue")

p <- ggplot(data = gapminder)
p

p <- ggplot(data = gapminder,
            mapping = aes(x = gdpPercap, #łączy oś x ze zmienną gdpPercap, inaczej położenia na osi x reprezentuje wartosć zmiennej gdpPercap
                y = lifeExp)) #łączy oś y ze zmienną lifeExp, inaczej położenia na osi y reprezentuje wartosć zmiennej lifeExp
p

p + geom_point() # dodaje warstwę z geometrią

p + geom_point() +  # dodaje warstwę z punktami
  geom_smooth() # dodaje kolejną warstwę z linią trendu
## `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Krok po kroku 1. Przekazujemy funkcji ggplot dane do narysowania wykresu 2. Przekazujemy funkcji ggplot jakie relacje chcemy zobaczyc na wykresie 3. Przekazujemy funkcji ggplot jak chcemy zobaczyć relacje na wykresie 4. Potrzebujemy warstwy z geometrią 5. Używamy dodatkowych funkcji żeby dopasować skale, etykiety, tytuły itp.

Geometrie dziedziczą informacje przekazane funkcji ggplot.

ggplot(data = gapminder,
            mapping = aes(x = gdpPercap,
                y = lifeExp)) +
  geom_point() +
  geom_smooth() +
  scale_x_log10()
## `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Estetyki wiążą dane z elementami graficznymi dlatego jeśli chcemy ustalić elementy graficzne nie wiążąc ich z danymi musimy to zrobić poza funkcją aes()

ggplot(data = gapminder,
            mapping = aes(x = gdpPercap,
                y = lifeExp,
                color = continent)) +
  geom_point() +
  geom_smooth() +
  scale_x_log10()
## `geom_smooth()` using method = 'loess' and formula = 'y ~ x'

Funkcja aes() służy wyłącznie do mapowania czyli wiązania elementów graficznych z danymi. Nie należy jej używać do ustalania konkretnych wartosci.

ggplot(data = gapminder,
            mapping = aes(x = gdpPercap,
                y = lifeExp,
                color = "blue")) +
  geom_point() +
  geom_smooth() +
  scale_x_log10()
## `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

ggplot(data = gapminder,
        mapping = aes(x = gdpPercap,
                      y = lifeExp),
                  color = "orange") + # być może coś się zmieniło bo funkcje geom zdają się już nie dziedziczyć sztywno ustawionej wartości atrybutu wizualnego poza aes
  geom_point(color = "purple") +
  geom_smooth() +
  scale_x_log10()
## `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Użycie alpha i scales

p <- ggplot(data = gapminder,
       mapping = aes(x = gdpPercap, 
                     y = lifeExp))

p + geom_point(alpha = 0.3) +
  geom_smooth(method = "gam") +
  scale_x_log10(labels = scales::dollar) + # modyfikuje skalę na logaytmiczną a etykiedy na dolary amerykańskie
  labs(x = "GDP per capita",
       y = "przeciętne dalsze trwanie życia",
       title = "Wzrost ekonomiczny i przeciętne dalsze trwanie życia",
       subtitle = "punkt danych to kraj-rok",
       caption = "źródło: Gapminder") 
## `geom_smooth()` using formula = 'y ~ s(x, bs = "cs")'

p <- ggplot(data = gapminder,
       mapping = aes(x = gdpPercap, 
                     y = lifeExp))

p + geom_point(alpha = 0.3) +
  scale_x_log10(labels = scales::dollar) +
   geom_smooth(method = "lm") +
  labs(x = "GDP per capita",
       y = "przeciętne dalsze trwanie życia",
       title = "Wzrost ekonomiczny i przeciętne dalsze trwanie życia",
       subtitle = "punkt danych to kraj-rok",
       caption = "źródło: Gapminder") 
## `geom_smooth()` using formula = 'y ~ x'

W przypadku geom_smooth Estetyka fill kontroluje kolor obszaru błędu standardowego

p <- ggplot(gapminder,
            aes(x = gdpPercap,
                y= lifeExp,
                color = continent,
                fill = continent)) 

p <- p + geom_point() +
  geom_smooth() +
  scale_x_log10(labels = scales::dollar)

Każda mapowana zmienna ma swoją skalę. Ggplot automatycznie dodaje legendy dla mapowań.

różne poziomy determinowania estetyk mają różne konsekwencje

ggplot(data = mpg,  mapping = aes(x = displ, y = hwy)) + 
  geom_point() +
  geom_smooth()
## `geom_smooth()` using method = 'loess' and formula = 'y ~ x'

ggplot() + 
  geom_point(data = mpg,  mapping = aes(x = displ, y = hwy)) +
  geom_smooth()

Obiekty graficzne geom_

ggplot(data = faithful) +
  geom_histogram(aes(x = eruptions))
## `stat_bin()` using `bins = 30`. Pick better value with `binwidth`.

estetyki dla każdego obiektu geometycznego zapisane są w dokumentacji

geom_point() understands the following aesthetics (required aesthetics are in bold):

x

y

alpha

colour

fill

group

shape

size

stroke

?geom_histogram

Współrzędne

bar <- ggplot(data = diamonds) + 
  geom_bar(mapping = aes(x = cut, fill = cut), 
           show.legend = FALSE, 
           width = 1 ) + 
  theme(aspect.ratio = 1) + 
  labs(x = NULL, y = NULL) 
bar

bar + coord_flip() 

bar + coord_polar()

Współrzędne w kontekscie map

UWAGA MOŻE WYMAGAĆ INSTALACJI DODATKOWEJ BIBLIOTEKI

ggplot(map_data("world", region = 'Russia'), 
        aes(long, lat, group = group)) +
  geom_polygon(fill = "white", 
               color = "black")

ggplot(map_data("world",
                region = 'Russia'), 
       aes(long, 
           lat, 
           group = group)) +
  geom_polygon(fill = "white",
               color = "black") +
  coord_quickmap()

Skale

skale kolorów

Kolorom poświęcimy więcej miejsca w przyszłości, w tym momencie tylko kilka przykładów

scale_color scale_color_brewer() RColorBrewer::display.brewer.all()

ggplot(data = mpg) + 
  geom_point( mapping = aes(x = displ, y = hwy, color = class)) +
  scale_color_brewer(palette ="Set3") # zmienia z domyślnego koloru na wybraną paletę 

osie

?scale_x_continuous()

ggplot(mpg) + 
  geom_point(aes(x = displ, y = hwy, color = class)) +
  scale_color_brewer(palette ="BrBG") +
  scale_x_continuous(breaks = (c(2, 5.5, 7))) # ustalamy własne przedziały tworząc wektor liczb funkcją c()

zadanie - zastosujmy scale_x_discrete do danych mpg

?scale_x_discrete()

panele - facets

Pozwalają uniknąć overplotting a także lepiej dostrzec pewne zależności w danych

porównajmy:

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, y = hwy, colour = class))

z poniższym wykresem:

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, y = hwy)) +
  facet_wrap(~ class)

facet_wrap() mapuje jedną zmienną na panele

mapowanie interakcji dwóch zmiennych na panele funkcją facet_grid()

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, 
                           y = hwy))  +
  facet_grid(cyl ~ class)

Zadanie PAnteon wykres fasetowany

Weźmy dane panteon i stwórzmy wykres panelowy prezentujacy liczbę kobiet i mężczyzn z każdego kontynentu. Niech płci różnią się kolorem a każdy panel reprezentuje jeden kontynet.

Etykiety

3etykiety dodajemy funkcją labs

labs(title = ““) # dodaje tytuł

labs(subtitle = ““) # dodaje podtytuł

labs(caption = ““) # dodaje kom

labs(x = ““, y =”“, colour =”“) # zastepuje tytuły osi i w legendzie

Dodajmy tytuł i podpis pod wykresem:

ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, y = hwy)) +
  labs(title = "Wydajność na autostradzie a pojemność",
       caption = "źródło: dane mpg",
       x = "pojemność", 
       y = "wydajność na autostradzie",
       colour = "klasa")

Zapisywanie wykresów funkcją ggsave

ggsave(“my-plot.pdf”) # > zapisue 6 x 3.71 cali

?ggsave # charakterystki wykresu w pliku docelowym i miejsce zapisania wykresu można ustalić

#ustawienie eval = FALSE oznacza że ten segment nie zostanie wykonany przy renderowaniu będziemy o tym mówić więcej na zajęciach  o rmarkdown

ggsave("rys 1.pdf", 
       plot = wykres, 
       device=cairo_pdf, #cairo_pdf jest jednym z urządzeń (device) zapisujących wykres do właściwego formatu, inaczej niż pdf cairo_pdf zapewnia właściwe wyświetlenie polskich znaków można użyć różnych urzadzeń sprawdźmy funkcją ?device
       width = 6, #szerokość w calach
       height=6, # wysokość w calach
       dpi = 300, # ten paramter może być istotny jeśli wykres ma być drukowany
       units = "in",  
       #path = ) # tu podajemy ścieżkę do folderu gdzie ma zostać zapisany plik
       #ścieżkę można ustawić globalnie dla całego pliku rmd tak że wszystkie wykresy zapiszą się automatycznie w wybranym folderze
       #będziemy będziemy o tym mówić więcej na zajęciach  o rmarkdown

Themes - layouty

ggplot zawiera wiele własnych szablonów istnieją także pakiety zawierające dodatkowe layouty jak ggthemes

#
#install.packages("ggthemes")
library(ggthemes)
ggplot(data = mpg) + 
  geom_point(mapping = aes(x = displ, y = hwy)) +
  labs(title = "Wydajność na autostradzie a pojemność",
       caption = "źródło: dane mpg",
       x = "pojemność", 
       y = "wydajność na autostradzie",
       colour = "klasa") + # theme jest kolejną warstwą którą dodajemy plusem
       theme_economist()

Praca domowa:

Co po zajęciach?

Plan minimum:

Ściągawka ggplot

Plan dla ambitnych:

Rozdział 10 Grafika w: Long, J. D. (2020). Język R: Receptury: analiza danych, statystyka i przetwarzanie grafiki, (K. Sawka, Tłum.). Helion SA.

to samo online po angielsku

Co przed następnymi zajęciami?

Plan minimum:

Ściągawka dplyr

Plan dla ambitnych:

Rozdział 3 Przekształcanie danych za pomocą pakieu dplyr w: Wickham, H., & Grolemund, G. (2020). Język R: Kompletny zestaw narzędzi dla analityków danych (J. Zatorska, Tłum.). Wydawnictwo Helion.

to samo online po angielsku